package com.yxf.variousshapes3d.shapes;

import android.graphics.Color;

import com.yxf.variousshapes3d.Point;

import java.nio.FloatBuffer;

import static android.opengl.GLES20.GL_TRIANGLE_STRIP;
import static android.opengl.GLES20.glDrawArrays;

public class Ball extends BaseShape {
    private float radius;
    private int circleCount;
    private float angleStep;

    private float[] vertices;
    private FloatBuffer vertexData;

    private final int bottomColor = Color.BLUE;
    private final int topColor = Color.GREEN;
    private int pointCount = 0;

    public Ball(Point center, float radius, int circleCount) {
        super(center);
        this.radius = radius;
        this.circleCount = circleCount;

        angleStep = (float) (Math.PI * 2 / circleCount);


    }

    @Override
    public void initWithoutLock() {
        int br = Color.red(bottomColor);
        int bg = Color.green(bottomColor);
        int bb = Color.blue(bottomColor);
        int ba = Color.alpha(bottomColor);

        int tr = Color.red(topColor);
        int tg = Color.green(topColor);
        int tb = Color.blue(topColor);
        int ta = Color.alpha(topColor);

        int zCount = circleCount / 2 + 1;
        int cCount = circleCount + 1;
        int len = POSITION_COMPONENT_COUNT + COLOR_COMPONENT_COUNT;
        pointCount = zCount * cCount * 2;
        vertices = new float[len * pointCount];
        int i = 0;
        for (int k = 0; k < zCount; k++) {
            float zAngle = (float) (-Math.PI / 2 + k * angleStep);
            float r = (float) (radius * Math.cos(zAngle));
            for (int j = 0; j < cCount; j++) {
                int index;
                if (k == 0) {
                    index = i / len;
                    vertices[i++] = center.x;
                    vertices[i++] = center.y;
                    vertices[i++] = center.z - radius;
                    vertices[i++] = br;
                    vertices[i++] = bg;
                    vertices[i++] = bb;
                    vertices[i++] = ba;
                    i += len;
                } else {
                    index = i / len;
                    vertices[i++] = center.x + (float) (r * Math.cos(j * angleStep));
                    vertices[i++] = center.y + (float) (r * Math.sin(j * angleStep));
                    vertices[i++] = center.z + (float) (radius * Math.sin(zAngle));
                    vertices[i++] = getMixtureColor(br, tr, index, pointCount);
                    vertices[i++] = getMixtureColor(bg, tg, index, pointCount);
                    vertices[i++] = getMixtureColor(bb, tb, index, pointCount);
                    vertices[i++] = getMixtureColor(ba, ta, index, pointCount);

                    int strip = len * 2 * cCount;
                    int t = i - len;
                    vertices[i++ - strip] = vertices[t++];
                    vertices[i++ - strip] = vertices[t++];
                    vertices[i++ - strip] = vertices[t++];
                    vertices[i++ - strip] = vertices[t++];
                    vertices[i++ - strip] = vertices[t++];
                    vertices[i++ - strip] = vertices[t++];
                    vertices[i++ - strip] = vertices[t++];
                }
            }
        }
        vertexData = encodeVertices(vertices);
    }

    private float getMixtureColor(int firstColor, int secondColor, int index, int count) {
        return (firstColor + (secondColor - firstColor) * index / count) / 255f;
    }

    @Override
    protected FloatBuffer getVertexData() {
        return vertexData;
    }

    @Override
    protected void drawArrays() {
        glDrawArrays(GL_TRIANGLE_STRIP, 0, pointCount);
    }

    @Override
    protected void preDraw() {

    }

    @Override
    protected void afterDraw() {

    }
}
